package com.ocean.proxy.api.service;

import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collections;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Set;

import org.apache.commons.codec.digest.DigestUtils;
import org.apache.commons.lang.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;

import com.ocean.core.common.system.ErrorCode;
import com.ocean.core.common.system.SystemContext;
import com.ocean.core.common.threadpool.Parameter;
import com.ocean.core.common.threadpool.workthread.AsynAbstractTask;
import com.ocean.persist.api.proxy.AdPullException;
import com.ocean.persist.api.proxy.JoinDSPEmu;
import com.ocean.persist.api.proxy.adview.AdviewAdContent;
import com.ocean.persist.api.proxy.adview.AdviewAdPullParams;
import com.ocean.persist.api.proxy.adview.AdviewAdPuller;
import com.ocean.persist.api.proxy.adview.AdviewAdResponse;
import com.ocean.persist.api.proxy.adview.AdviewImage;
import com.ocean.persist.api.proxy.adview.AdviewNative;
import com.ocean.persist.common.ProxyConstants;
import com.ocean.persist.model.proxy.DSPPosition;
import com.ocean.proxy.api.base.AbstractAdSupplier;
import com.ocean.proxy.api.helper.InvenoIdGenerator;
import com.ocean.proxy.thrift.entity.AdContent;
import com.ocean.proxy.thrift.entity.AdImg;
import com.ocean.proxy.thrift.entity.AdMutiAction;
import com.ocean.proxy.thrift.entity.AdRecomReply;
import com.ocean.proxy.thrift.entity.AdRecomReq;
import com.ocean.proxy.thrift.entity.AdSpaceType;
import com.ocean.proxy.thrift.entity.AdUserInfo;
import com.ocean.proxy.thrift.entity.UserAdSpaceAttri;
@Component(value="adviewAdSupplier")
public class AdviewAdSupplier extends AbstractAdSupplier{
    @Autowired
	private AdviewAdPuller adviewAdPuller;
	private final Logger logger = LoggerFactory.getLogger(getClass());
	private static Map<AdSpaceType, Integer> pt = new HashMap<AdSpaceType, Integer>(6);
	
	private static Map<AdSpaceType, Integer> at = new HashMap<AdSpaceType, Integer>();
	
	private static Map<Integer, AdSpaceType> at1 = new HashMap<Integer, AdSpaceType>();
	private static Map<Integer, Integer> actType = new HashMap<Integer, Integer> ();
	static{
		pt.put(AdSpaceType.BANNER, 0);
		pt.put(AdSpaceType.INTERSTITIAL, 1);
		pt.put(AdSpaceType.OPENING, 4);
		pt.put(AdSpaceType.INFOFLOW, 6);
		
		at.put(AdSpaceType.BANNER, 0);
		at.put(AdSpaceType.OPENING, 5);
		at.put(AdSpaceType.INTERSTITIAL, 3);
		at.put(AdSpaceType.INFOFLOW, 8);
		
		at1.put(0, AdSpaceType.BANNER);
		at1.put(5, AdSpaceType.OPENING);
		at1.put(3, AdSpaceType.INTERSTITIAL);
		at1.put(8, AdSpaceType.INFOFLOW);
		
		actType.put(1, ACTION_WEB);
		actType.put(2, ACTION_APP);
		actType.put(4, ACTION_WEB);
		actType.put(8, ACTION_WEB);
		actType.put(16, ACTION_WEB);
		actType.put(32, ACTION_CALL);
		actType.put(64, ACTION_VIDEO);
	}
	
	public AdRecomReply invoke(InvokeAttribute attribute) throws AdPullException {
		
		AdRecomReq adreq = attribute.getAdreq();
		DSPPosition positionInfo = attribute.getDspPosition();
		// 参数转换
		AdviewAdPullParams params = parseParams(adreq, positionInfo);
		// 调用API
		AdviewAdResponse response = (AdviewAdResponse) adviewAdPuller.api(params,adreq.getHash(),String.valueOf(adreq.getUserAdSpaceAttri().getAdSpaceId()));
		return parseResult(response, adreq);
	}
	
	private AdRecomReply parseResult(AdviewAdResponse response, AdRecomReq adreq)
			throws AdPullException {
		
		if(response == null){
			return null;
		}
		// 返回对象
		AdRecomReply recomReply = new AdRecomReply();
		recomReply.setStatus(status);
		
		List<AdviewAdContent> ads = response.getAd();
		if(response.getRes()==0){
			throw new AdPullException("joinDSP:av ad request error,return massage:"+response.getMg());
		}
		if(ads == null || ads.isEmpty()){
			return null;
		}
		// 目前只能是一条
		AdviewAdContent ad = ads.get(0);
//		0=>图片横幅广告 1=>混合文字链 2=>图形文字链（带行为图标） 3=>图片插屏广告
//		4=>html 广告 5=>开屏纯图片 8=>原生广告 100=>富媒体插屏
		int at = ad.getAt();
		logger.info("joinDSP:av ad request, return bidid:{}",ad.getAdi());
		// 素材类型不匹配
		AdSpaceType spaceType = at1.get(at);
		AdSpaceType reqType = adreq.getUserAdSpaceAttri().getSpaceType();
		if(spaceType == null || spaceType != reqType){
			logger.info("joinDSP:av ad request ad type:{}, return adType:{}",reqType,at);
			return null;
		}
		//----------------BEGIN 常规选项--------------
		AdContent content = new AdContent();
		String linkurl = ad.getAl();
		content.setLinkurl(linkurl);
		//content.setAdId(InvenoIdGenerator.genThirdDspId(SystemContext.getDynamicPropertyHandler().getInt(ProxyConstants.PROXY_SERVER_NODE_INDEX,100)));
		Map<String, List<String>> map = new HashMap<String, List<String>>();
		// 点击监测
		List<String> click = ad.getEc();
		if(click == null){
			click = new ArrayList<String>();
		}
		map.put(CLICK, click);
		// 曝光监测
		List<String> show = new ArrayList<String>();
		Map<String, List<String>> es = ad.getEs();
		if(es != null && !es.isEmpty()){
			
			Set<String> keys = es.keySet();
			for (String key : keys) {
				show.addAll(es.get(key));
			}
		}
		map.put(SHOW, show);
		content.setThirdReportLinks(map);
		// 广告图片
		List<AdImg> imgs = new ArrayList<AdImg>();
		AdMutiAction action = new AdMutiAction();
		action.setLinkurl(linkurl);
		//设置交互类型
		Integer type=actType.get(ad.getAct());
		action.setType(type==null?ACTION_WEB:type);
		
		
		content.setMarketTitle(defTitle);
		content.setGuideTitle(defTitle);
		action.setGuideTitle(defTitle);
		
		if(StringUtils.isNotEmpty(ad.getAti())){
			content.setMarketTitle(ad.getAti());
			content.setGuideTitle(ad.getAti());
			action.setGuideTitle(ad.getAti());
		}
		if(StringUtils.isNotEmpty(ad.getAst())){
			if(StringUtils.isEmpty(content.getMarketTitle())){
				content.setMarketTitle(ad.getAst());
				action.setGuideTitle(ad.getAst());
			}
			content.setGuideTitle(ad.getAst());
			
		}
		// 广告尺寸 	320x50 
		String as = ad.getAs();
		Integer w = null, h = null;
		if(StringUtils.isNotEmpty(as) && as.indexOf("x") > 0){
			String[] ass = as.split("x");
			w = Integer.valueOf(ass[0]);
			h = Integer.valueOf(ass[1]);
		}
		// 图片广告时，图片的 URL 地址 
		List<String> api = ad.getApi();
		if(api != null){
			for(String url : api){
				AdImg img = new AdImg();
				img.setSrc(url);
				if(StringUtils.isNotEmpty(as)){
					img.setWidth(w);
					img.setHeight(h);
				}
				imgs.add(img);
			}
		}
		//图标
		action.setCpIcon(ad.getAic());
		//----------------END 常规选项--------------
		if(at == 8){
			AdviewNative nat = ad.getNat();
			List<AdviewImage> images = nat.getImages();
			if(images != null){
				for (AdviewImage adviewImage : images) {
					AdImg img = new AdImg();
					img.setSrc(adviewImage.getUrl());
					img.setWidth(adviewImage.getW());
					img.setHeight(adviewImage.getH());
					imgs.add(img);
				}
			}
			
			AdviewImage icon = nat.getIcon();
			if(icon != null){
				action.setCpIcon(icon.getUrl());
				if(imgs.isEmpty()){
					AdImg img = new AdImg();
					img.setSrc(icon.getUrl());
					img.setWidth(icon.getW());
					img.setHeight(icon.getH());
					imgs.add(img);
				}
			}
			AdviewImage logo = nat.getLogo();
			if(logo != null){
				AdImg img = new AdImg();
				img.setSrc(logo.getUrl());
				img.setWidth(logo.getW());
				img.setHeight(logo.getH());
				content.setLogoImg(img);
			}
			if(StringUtils.isNotEmpty(nat.getTitle())){
				content.setGuideTitle(nat.getTitle());
				action.setGuideTitle(nat.getTitle());

			}
			if(StringUtils.isNotEmpty(nat.getDesc())){
				content.setMarketTitle(nat.getDesc());
				content.setContent(nat.getDesc());
			}
			
		}
		// 图片地址
		content.setImglist(imgs);
		content.setMutiAction(Collections.singletonList(action));
		recomReply.setAd_content(content);
		return recomReply;
	}
	
	private AdviewAdPullParams parseParams(AdRecomReq adreq, DSPPosition pos) throws AdPullException{
		
		UserAdSpaceAttri attri = adreq.getUserAdSpaceAttri();
		AdUserInfo userInfo = adreq.getUserinfo();
		AdviewAdPullParams params = new AdviewAdPullParams();
		params.setPt(pt.get(attri.getSpaceType()));
		params.setW(attri.getSpaceWidth());
		params.setH(attri.getSpaceHeight());
		if(StringUtils.isNotEmpty(userInfo.getClient_ip())){
			params.setIp(userInfo.getClient_ip());
		}
		if(StringUtils.isNotEmpty(userInfo.getOsversion())){
			params.setBdr(userInfo.getOsversion());
		}
		if(StringUtils.isNotEmpty(userInfo.getPhonemodel())){
			params.setTp(encode(userInfo.getPhonemodel()));
		}
		if(StringUtils.isNotEmpty(userInfo.getUa())){
			params.setUa(encode(userInfo.getUa()));
		}
		/* 
		 * 0=>任意(Native或html5)
	       1=>html5广告(非h5我们会转成h5广告下发)
		 * 
		 * */
	    params.setHtml5(attri.getH5type()==1?1:0);//h5type 0：h5和h5都可以：1：只拉h5; 2:只拉非h5
		
		params.setTime(System.currentTimeMillis());
		params.setAt(at.get(attri.getSpaceType()));
		String osCode = userInfo.getOs();
		// 只有原生的才有广告位
		if(attri.getSpaceType() == AdSpaceType.INFOFLOW){
			params.setPosId(pos.getPos());
		}
		
		// 如果是ios
		int os = 0;
		if(OS_IOS.equals(osCode)){
			// ios 必填信息
			params.setIdfa(userInfo.getIdfa());
			params.setSn(userInfo.getIdfa());
			params.setIdfv(userInfo.getIdfa());
			os = 1;
		}else if(OS_ANDROID.equals(osCode)){
			params.setAndid(userInfo.getAdid());
			// 0=>支持安卓设备传IMEI和AndroidId 1=>支持安卓设备传Google Advertising Id
			params.setAndt(0);
			params.setSn(userInfo.getImei());
		}
		params.setOs(os);
		params.setN(1);// 返回的广告条数
		
		if(StringUtils.isNotEmpty(userInfo.getMac())){
			params.setMc(userInfo.getMac());
		}
		if(StringUtils.isNotEmpty(adreq.getNet())){
			params.setNt(adreq.getNet());
		}
		if(StringUtils.isNotEmpty(userInfo.getMobile())){
			// 46000、46002、46007=>中国移动 
			// 46001、46006=>中国联通 46003、46005=>中国电信没有就填""字符串
	    	String carrier=mobiles.get(userInfo.getMobile());
	    	params.setNop(carrier==null?"46020":carrier);
		}else{
			params.setNop("46020");
		}
		if(StringUtils.isEmpty(pos.getText1())||StringUtils.isEmpty(pos.getText2())){
			throw new AdPullException(ErrorCode.PARAM_ERROR,"App id or App package name is empty!");
		}
		params.setAppid(pos.getText1());
		//0=>手机,1=>平板
        params.setTab(0);
		params.setPack(pos.getText2());
		// 0=>正式模式 1=>测试模式
		params.setTm(SystemContext.getDynamicPropertyHandler().getInt(ProxyConstants.ADVIEW_IS_TEST,0));

		params.setBaseFloor(pos.getSettlementPrice() * 100);
		
		//生成token,MD5(appid+sn+os+nop+pack+time+secretKey) 
		StringBuilder md5str = new StringBuilder();
		md5str.append(params.getAppid());
		md5str.append(params.getSn());
		md5str.append(params.getOs());
		md5str.append(params.getNop());
		md5str.append(params.getPack());
		md5str.append(params.getTime());
		md5str.append(SystemContext.getDynamicPropertyHandler().get(ProxyConstants.ADVIEW_SECRET));
		String token = DigestUtils.md5Hex(md5str.toString());
		params.setToken(token);
		return params;
	}

	public AdviewAdPuller getAdviewAdPuller() {
		return adviewAdPuller;
	}

	public void setAdviewAdPuller(AdviewAdPuller adviewAdPuller) {
		this.adviewAdPuller = adviewAdPuller;
	}

}
